package com.ruoyi.combat.util;

import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.RuntimeUtil;
import cn.hutool.json.JSONUtil;
import com.ruoyi.combat.domain.useralignment.CombatRelationWb;
import com.ruoyi.combat.domain.userlocation.CombatRelation;
import com.ruoyi.combat.domain.useralignment.CombatRelationZh;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;

import java.io.*;
import java.nio.charset.Charset;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.*;
import java.util.stream.Collectors;

@Component
public class UserLocationUtil {

    @Value("${keti5.funcation0Path}")
    private String path;

    private String antiPath;

    private static final String cmd1 = "python -u network_alignment.py --source_dataset dataspace/douban/online/graphsage --target_dataset dataspace/douban/offline/graphsage --groundtruth dataspace/douban/dictionaries/groundtruth REGAL";
    private static final String method1 = "REGAL";
    private static final String method2 = "BigAlign";


    /**
     * 身份识别算法1
     */
    public void identifyMethod(String type, List<CombatRelationWb> wbList, List<CombatRelationZh> zhList) {
//        writeWbFile(path, wbList);
//        writezhFile(path, zhList);


        if ("1".equals(type)) {

        } else {

        }


    }

    /**
     * @param path
     * @param wbList
     */
    public String writeWbFile(String path, String folder, List<CombatRelationWb> wbList, String wbUserId) {
        Set<String> ids = new HashSet();
        for (CombatRelationWb wb : wbList) {
            String userid = wb.getUserid();
            String targetid = wb.getTargetid();
            ids.add(userid);
            ids.add(targetid);
        }
        // ids转换为list
        String[] array = (String[]) ids.toArray(new String[0]);
        Map<String, Integer> id2idx = new HashMap<>();
        List<Map<String, String>> nodes = new ArrayList<>();
        for (int i = 0; i < array.length; i++) {
            id2idx.put(array[i], i);
            Map<String, String> node = new HashMap<>();
            node.put("id", array[i]);
            nodes.add(node);
        }
        List<Map<String, String>> links = new ArrayList<>();
        for (CombatRelationWb wb : wbList) {
            String userid = wb.getUserid();
            String targetid = wb.getTargetid();
            Map<String, String> link = new HashMap<>();
            link.put("source", userid);
            link.put("target",targetid);
            links.add(link);
        }

        String filePath = path + folder + File.separator + "weibo" + File.separator;
        Map<String, Object> G = new HashMap<>();
        G.put("directed", false);
        G.put("multigraph", false);
        G.put("graph", Collections.EMPTY_MAP);
        G.put("nodes", nodes);
        G.put("links", links);




        FileUtil.writeUtf8String(JSONUtil.toJsonStr(G), filePath + "G.json");
        FileUtil.writeUtf8String(JSONUtil.toJsonStr(id2idx), filePath + "id2idx.json");
        return filePath;

//        List<String> objects = new ArrayList<>();
//        FileUtil.writeLines(objects,filePath+"groundtruth", Charset.defaultCharset());
//        FileUtil.writeLines(objects,filePath+"KnownAnchor.dict", Charset.defaultCharset());
    }

    public String writezhFile(String path, String folder, List<CombatRelationZh> wbList, String zhUserId) {
        Set<String> ids = new HashSet();
        for (CombatRelationZh wb : wbList) {
            String userid = wb.getUserid();
            String targetid = wb.getTargetid();
            ids.add(userid);
            ids.add(targetid);
        }
        // ids转换为list
        String[] array = (String[]) ids.toArray(new String[0]);
        Map<String, Integer> id2idx = new HashMap<>();
        List<Map<String, String>> nodes = new ArrayList<>();
        for (int i = 0; i < array.length; i++) {
            id2idx.put(array[i], i);
            Map<String, String> node = new HashMap<>();
            node.put("id", array[i]);
            nodes.add(node);
        }
        List<Map<String, String>> links = new ArrayList<>();
        for (CombatRelationZh wb : wbList) {
            String userid = wb.getUserid();
            String targetid = wb.getTargetid();
            Map<String, String> link = new HashMap<>();
            link.put("source", userid);
            link.put("target",targetid);
            links.add(link);
        }

        String filePath = path + folder + File.separator + "zhihu" + File.separator;
        Map<String, Object> G = new HashMap<>();
        G.put("directed", false);
        G.put("multigraph", false);
        G.put("graph", Collections.EMPTY_MAP);
        G.put("nodes", nodes);
        G.put("links", links);




        FileUtil.writeUtf8String(JSONUtil.toJsonStr(G), filePath + "G.json");
        FileUtil.writeUtf8String(JSONUtil.toJsonStr(id2idx), filePath + "id2idx.json");
        return filePath;
    }

    /**
     * 生成不带文件扩展名的文件
     * @param path 文件路径基础目录
     * @param folder 子文件夹名称
     * @param wbIdList 第一个ID列表
     * @param zhIdList 第二个ID列表
     * @param append 是否以追加模式写入文件
     * @return 文件完整路径
     * @throws IllegalArgumentException 如果输入参数无效
     * @throws IOException 如果文件写入失败
     */
    public static String writeGroundTruthFile(String path, String folder, List<String> wbIdList, List<String> zhIdList, boolean append) throws IOException {
        // 边界条件校验
        if (path == null || path.isEmpty() || folder == null || folder.isEmpty()) {
            throw new IllegalArgumentException("路径或文件夹名称不能为空");
        }
        // 构建文件路径
        String filePath = Paths.get(path + folder , "dictionaries", "groundtruth").toString();

        // 确保父目录存在
        Files.createDirectories(Paths.get(filePath).getParent());

        // 写入文件
        try (BufferedWriter writer = new BufferedWriter(new FileWriter(filePath, append))) {
            StringBuilder content = new StringBuilder();
            for (int i = 0; i < wbIdList.size(); i++) {
                content.append(wbIdList.get(i)).append(" ").append(zhIdList.get(i)).append("\n");
            }
            writer.write(content.toString());
            return filePath;
        } catch (IOException e) {
            throw new IOException("文件写入失败: " + e.getMessage(), e);
        }
    }

    /**
     * 抗关联算法
     */
    public void antiCorrelationMethod(String type, String userid, Integer addNum, Integer similarNum,
                                      double ratio, List<CombatRelationWb> wbList, List<CombatRelationZh> zhList, List<Map> index_result) {
        List<String> wbDataList = new ArrayList<>();
        for (CombatRelationWb wb : wbList) {
            String userid1 = wb.getUserid();
            String targetid = wb.getTargetid();
            String data = userid1 + " " + targetid;
            wbDataList.add(data);
        }
        FileUtil.writeLines(wbDataList, antiPath + File.separator + "data" + File.separator + "initial" + File.separator + "weibo.cites", Charset.defaultCharset());
        List<String> zhDataList = new ArrayList<>();
        for (CombatRelationZh wb : zhList) {
            String userid1 = wb.getUserid();
            String targetid = wb.getTargetid();
            String data = userid1 + " " + targetid;
            zhDataList.add(data);
        }
        FileUtil.writeLines(zhDataList, antiPath + File.separator + "data" + File.separator + "initial" + File.separator + "zhihu.cites", Charset.defaultCharset());
        List<String> cmdList = new ArrayList<>();
        if (antiPath.contains(":")) {
            String[] split = antiPath.split(":");
            String cmd0 = split[0] + ":";
            cmdList.add(cmd0);
        }
        String cmd1 = "cd " + path;

        cmdList.add(cmd1);

        executeCMD(cmdList);

//新增关系
    }


    public void executeCMD(List<String> commands) {
        String command = handlerCMD(commands);
        System.out.println(command);
        ProcessBuilder processBuilder = new ProcessBuilder(command);
        processBuilder.redirectErrorStream(true);
        try {
            Process process = processBuilder.start();
            String result = new BufferedReader(new InputStreamReader(process.getInputStream())).lines().collect(Collectors.joining(System.lineSeparator()));
            System.out.println(result);
            process.waitFor();
        } catch (IOException | InterruptedException e) {
            e.printStackTrace();
        }
    }

    /**
     * 处理命令行
     *
     * @param commands 使用 &&符号拼接多个命令行
     * @return 处理后的命令行
     */
    private static String handlerCMD(List<String> commands) {
        StringBuilder command = new StringBuilder();
        for (int i = 0; i < commands.size(); i++) {
            command.append(commands.get(i));
            if (i != commands.size() - 1) {
                command.append(" && ");
            }
        }
        return command.toString();
    }


}


